package com.zhang.crm.config;

import com.zhang.crm.filter.JWTFilter;
import com.zhang.crm.handler.ZhangAccessDeniedHandler;
import com.zhang.crm.handler.ZhangLoginFailureHandler;
import com.zhang.crm.handler.ZhangLoginSuccessHandler;
import com.zhang.crm.handler.ZhangLogoutSuccessHandler;
import com.zhang.crm.service.UserService;
import jakarta.annotation.Resource;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.logout.LogoutFilter;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.CorsConfigurationSource;
import org.springframework.web.cors.UrlBasedCorsConfigurationSource;

import java.util.Arrays;

@Configuration
public class SecurityConfig {
    @Resource
    private ZhangLoginSuccessHandler zhangLoginSuccessHandler;

    @Resource
    private ZhangLogoutSuccessHandler zhangLogoutSuccessHandler;

    @Resource
    private ZhangAccessDeniedHandler zhangAccessDeniedHandler;

    @Resource
    private ZhangLoginFailureHandler zhangLoginFailureHandler;
    @Resource
    private UserService userService;

    @Resource
    private JWTFilter jwtFilter;

    /**
     * security跨域支持
     * @return
     */
    @Bean
    public CorsConfigurationSource corsConfigurationSource() {
        CorsConfiguration corsConfiguration = new CorsConfiguration();
        corsConfiguration.setAllowedOrigins(Arrays.asList("*"));  //允许的来源
        corsConfiguration.setAllowedMethods(Arrays.asList("*")); //允许的方法
        corsConfiguration.setAllowedHeaders(Arrays.asList("*")); //允许的请求头

        UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
        source.registerCorsConfiguration("/**", corsConfiguration); //任何请求都支持
        return source;
    }
    /**
     * 密码加密器
     * @return
     */
    @Bean
    public PasswordEncoder passwordEncoder() {
        return new BCryptPasswordEncoder();
    }

    /**
     * 用户认证过滤器
     */
    @Bean
    public UserDetailsService userDetailsService() {
        //数据库用户配置
        return new UserDetailsService() {
            @Override
            public UserDetails loadUserByUsername(String loginAct) throws UsernameNotFoundException {
                //查询用户
                UserDetails userDetails = userService.getUser(loginAct);
                return userDetails;
            }
        };
    }

    @Bean
    public SecurityFilterChain securityFilterChain(HttpSecurity httpSecurity, CorsConfigurationSource corsConfigurationSource) throws Exception {
        return httpSecurity
                .formLogin( (formLogin) ->{  //登录配置
                    formLogin.loginProcessingUrl("/login")
                            .usernameParameter("loginAct")
                            .passwordParameter("loginPwd")
                            .successHandler(zhangLoginSuccessHandler)
                            .failureHandler(zhangLoginFailureHandler);


                })
                .logout((logout)->{ //退出配置
                    logout.logoutUrl("/logout")
                            .invalidateHttpSession(true)  //使session会话失效
                            .logoutSuccessHandler(zhangLogoutSuccessHandler)
                            ;
                })
                .authorizeHttpRequests( (authorize) ->{
                    authorize.requestMatchers("/toLogin","/test","/api/freeLogin").permitAll()
                            .anyRequest().authenticated(); //拦截所有
                })
                .exceptionHandling((exception) ->{  //异常控制
                    //访问拒绝
                    //exception.accessDeniedPage("/error.html"); //无权限访问拒绝
                    exception.accessDeniedHandler(zhangAccessDeniedHandler);



                })
                .csrf( (csrf)->{
                    csrf.disable(); //禁用跨站请求伪造
                })
                .cors((cors)-> {
                    cors.configurationSource(corsConfigurationSource);//配置跨域
                })
                //服务器禁用session
                .sessionManagement((session) ->{
                       session.sessionCreationPolicy(SessionCreationPolicy.STATELESS);
                   })
                .addFilterBefore(jwtFilter, LogoutFilter.class)
                .build();
    }
}
